﻿#pragma once

#include "../../MirControls/MirImageControl.h"
#include "../../../Shared/Enums.h"
#include "../../../Shared/Globals.h"
#include "../../MirControls/MirTextBox.h"
#include "../../MirControls/MirButton.h"
#include "../../MirControls/MirLabel.h"
#include "../../MirControls/MirItemCell.h"
#include "../../../Shared/Data/ItemData.h"
#include "../../../Shared/Data/ClientData.h"
#include "../../MirControls/MirControl.h"
#include <string>
#include <vector>
#include <cmath>
#include <limits>
#include <cctype>
#include <any>
#include <optional>
#include "../../../stringhelper.h"

//C# TO C++ CONVERTER NOTE: Forward class declarations:
namespace Client::MirScenes::Dialogs { class AuctionRow; }
namespace Client::MirScenes::Dialogs { class Filter; }

using namespace Client::MirControls;
using namespace Client::MirGraphics;
using namespace Client::MirNetwork;
using namespace Client::MirSounds;
namespace C = ClientPackets;


namespace Client::MirScenes::Dialogs
{
    class TrustMerchantDialog final : public MirImageControl
    {
    public:
        static bool UserMode;
        static MarketPanelType MarketType;

        unsigned int Amount = 0, MinConsignAmount = Globals::MinConsignment, MaxConsignAmount = Globals::MaxConsignment, MinBidAmount = Globals::MinStartingBid, MaxBidAmount = Globals::MaxStartingBid;

        static long long SearchTime;
        static long long MarketTime;

        MirTextBox *SearchTextBox, *PriceTextBox;
        MirButton *FindButton, *RefreshButton, *MailButton, *BuyButton, *SellNowButton, *CloseButton, *NextButton, *BackButton;
        MirImageControl *TitleLabel;
        MirLabel *ItemLabel, *PriceLabel, *SellerLabel, *PageLabel;
        MirLabel *DateLabel, *ExpireLabel;
        MirLabel *NameLabel, *TotalPriceLabel, *SplitPriceLabel;
        MirLabel *HelpLabel;
        MirLabel *TitleSalePriceLabel, *TitleSellLabel, *TitleItemLabel, *TitlePriceLabel, *TitleExpiryLabel;

        MirItemCell *ItemCell, *tempCell;
        static UserItem *SellItemSlot;
        MirButton *SellItemButton;

        std::vector<ClientAuction*> Listings = std::vector<ClientAuction*>();
        std::vector<ClientAuction*> GameShopListings = std::vector<ClientAuction*>();

        int Page = 0, PageCount = 0;
        static AuctionRow *Selected;
        std::vector<AuctionRow*> Rows = std::vector<AuctionRow*>(10);

        MirButton *UpButton, *DownButton, *PositionBar;
        MirButton *MarketButton, *ConsignmentButton, *AuctionButton, *GameShopButton;

        MirImageControl *FilterBox, *FilterBackground;

    private:
        const std::string consignmentText = std::string::Format("1. Consignment is {0} gold per item \r\n\r\n2. 1% of sale price is paid to Trust Merchant ", Globals::ConsignmentCost) + std::string::Format("at sale end\r\n\r\n3. Maximum {0} days of item sale registration until item is removed\r\n\r\n4. Maximum of unlimited ", Globals::ConsignmentLength) + std::string::Format("items allowed for sale\r\n\r\n5. Sale price can be set between: {0} - {1} gold", Globals::MinConsignment, Globals::MaxConsignment);

        const std::string auctionText = std::string::Format("1. Auction cost is {0} gold, max starting bid is {1} gold per item \r\n\r\n2. 1% of final bid price is paid to Trust Merchant ", Globals::AuctionCost, Globals::MaxStartingBid) + std::string::Format("at auction end\r\n\r\n3. Maximum {0} days of item sale registration, afterwards the item will be sent to highest bidder\r\n\r\n4. Maximum of unlimited ", Globals::ConsignmentLength) + std::string::Format("items allowed for auction\r\n\r\n");

        MirLabel *TotalGold;

    public:
        std::vector<Filter*> Filters = std::vector<Filter*>();

    private:
        std::vector<MirButton*> FilterButtons = std::vector<MirButton*>();
        std::vector<MirLabel*> FilterLabels = std::vector<MirLabel*>();

        int Skip = 0;
        int MaxLines = 19;
        int SelectedIndex = -1;
        int SelectedSubIndex = -1;

        int PossibleTotal = 0;
        int PosX = 0, PosMinY = 0, PosMaxY = 0;

    public:
        virtual ~TrustMerchantDialog()
        {
            delete SearchTextBox;
            delete PriceTextBox;
            delete FindButton;
            delete RefreshButton;
            delete MailButton;
            delete BuyButton;
            delete SellNowButton;
            delete CloseButton;
            delete NextButton;
            delete BackButton;
            delete TitleLabel;
            delete ItemLabel;
            delete PriceLabel;
            delete SellerLabel;
            delete PageLabel;
            delete DateLabel;
            delete ExpireLabel;
            delete NameLabel;
            delete TotalPriceLabel;
            delete SplitPriceLabel;
            delete HelpLabel;
            delete TitleSalePriceLabel;
            delete TitleSellLabel;
            delete TitleItemLabel;
            delete TitlePriceLabel;
            delete TitleExpiryLabel;
            delete ItemCell;
            delete tempCell;
            delete SellItemButton;
            delete UpButton;
            delete DownButton;
            delete PositionBar;
            delete MarketButton;
            delete ConsignmentButton;
            delete AuctionButton;
            delete GameShopButton;
            delete FilterBox;
            delete FilterBackground;
            delete TotalGold;
        }

        TrustMerchantDialog();

    private:
        void SetupFilters();

        void DrawFilters(int index, int subIndex);

        void PositionBar_OnMoving(std::any sender, MouseEventArgs *e);

        void UpdatePositionBar();

    public:
        void UpdateInterface();

    private:
        void SearchTextBox_KeyPress(std::any sender, KeyPressEventArgs *e);
        void SearchTextBox_KeyUp(std::any sender, KeyEventArgs *e);
        void SearchTextBox_KeyDown(std::any sender, KeyEventArgs *e);

    public:
        void TMerchantDialog(MarketPanelType type);

    private:
        void TextBox_TextChanged(std::any sender, EventArgs *e);

        void MirInputBox_KeyPress(std::any sender, KeyPressEventArgs *e);

        void ItemCell_Click();

    public:
        void Hide() override;
        void Show(bool gameshop = false);

        #pragma region AuctionRow
    public:
        class AuctionRow final : public MirControl
        {
        public:
            ClientAuction *Listing = nullptr;

            MirLabel *NameLabel, *PriceLabel, *SellerLabel, *ExpireLabel;
            MirImageControl *IconImage, *SelectedImage;
            bool Selected = false;

        private:
            Size *IconArea = new Size(34, 32);

        public:
            virtual ~AuctionRow()
            {
                delete Listing;
                delete NameLabel;
                delete PriceLabel;
                delete SellerLabel;
                delete ExpireLabel;
                delete IconImage;
                delete SelectedImage;
                delete IconArea;
            }

            AuctionRow();

        private:
            void AuctionRow_BeforeDraw(std::any sender, EventArgs *e);
        public:
            void UpdateInterface();
        protected:
            void Dispose(bool disposing) override;
        public:
            void Clear();
            void Update(ClientAuction *listing);
        protected:
            void OnMouseEnter() override;
            void OnMouseLeave() override;
        };
        #pragma endregion

    public:
        class Filter
        {
        private:
            int Index = -1;
            std::string Title = "";
            std::optional<ItemType> Type = ItemType::Nothing;
            short MinShape = 0;
            short MaxShape = std::numeric_limits<short>::max();

        public:
            int getIndex() const;
            void setIndex(int value);
            std::string getTitle() const;
            void setTitle(const std::string &value);
            std::optional<ItemType> getType() const;
            void setType(const std::optional<ItemType> &value);
            short getMinShape() const;
            void setMinShape(short value);
            short getMaxShape() const;
            void setMaxShape(short value);

            std::vector<Filter*> SubFilters = std::vector<Filter*>();
        };
    };
}
